package com.dishdex.menuhub.app.controller;

import com.dishdex.menuhub.app.domain.index.ActivityVO;
import com.dishdex.menuhub.app.domain.index.BannerVO;
import com.dishdex.menuhub.app.domain.index.ChannelVO;
import com.dishdex.menuhub.app.domain.index.IndexVO;
import com.dishdex.menuhub.app.domain.category.CategoryLevelOneVO;
import com.dishdex.menuhub.app.domain.dish.DishItemVO;
import com.dishdex.menuhub.app.util.CategoryConverter;
import com.dishdex.menuhub.app.util.DishConverter;
import com.dishdex.menuhub.module.module.category.entity.Category;
import com.dishdex.menuhub.module.module.category.service.CategoryService;
import com.dishdex.menuhub.module.module.dish.entity.Dish;
import com.dishdex.menuhub.module.module.dish.service.DishService;
import com.dishdex.menuhub.module.utils.Response;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.*;
import java.util.stream.Collectors;

/**
 * ClassName:
 * Package: com.dishdex.menuhub.app.controller
 * Description:
 *
 * @Author:
 * @Create 2025/11/9 14:56
 * @Version 1.0
 */
@RestController
public class IndexController {

    @Autowired
    private DishService dishService;

    @Autowired
    private CategoryService categoryService;

    private final ExecutorService executorService = Executors.newFixedThreadPool(5);

    /**
     * 首页数据接口：并行加载 Banner、频道、活动、菜品、分类数据
     */
    @RequestMapping("/dish/index")
    public Response index() {
        // 1. 启动所有异步任务
        CompletableFuture<List<BannerVO>> bannerFuture = CompletableFuture.supplyAsync(this::buildBanners, executorService);
        CompletableFuture<List<ChannelVO>> channelFuture = CompletableFuture.supplyAsync(this::buildChannels, executorService);
        CompletableFuture<List<ActivityVO>> activityFuture = CompletableFuture.supplyAsync(this::buildActivities, executorService);
        CompletableFuture<List<DishItemVO>> dishFuture = CompletableFuture.supplyAsync(this::loadDishes, executorService);
        CompletableFuture<List<CategoryLevelOneVO>> categoryFuture = CompletableFuture.supplyAsync(this::loadCategories, executorService);

        // 2. 等待所有任务完成
        try {
            CompletableFuture.allOf(bannerFuture, channelFuture, activityFuture, dishFuture, categoryFuture)
                    .join(); // join() 会抛出 CompletionException（非 checked exception）

            // 3. 所有任务成功完成，安全组装响应
            IndexVO indexVO = new IndexVO();
            indexVO.setBannerList(bannerFuture.join());
            indexVO.setChannelList(channelFuture.join());
            indexVO.setActivityList(activityFuture.join());
            indexVO.setDishList(dishFuture.join());
            indexVO.setCategoryList(categoryFuture.join());

            return new Response(1001, indexVO);

        } catch (Exception e) {
            // 统一处理异常：可能是任意一个异步任务抛出的
            String errorMessage = "首页数据加载失败";
            if (e.getCause() != null) {
                errorMessage += ": " + e.getCause().getMessage();
            }
            return new Response(4004, errorMessage);
        }
    }

    // ========== 私有方法：封装各数据加载逻辑 ==========

    private List<BannerVO> buildBanners() {
        List<BannerVO> list = new ArrayList<>();
        list.add(new BannerVO("https://ex1.com", "https://ex2.com"));
        list.add(new BannerVO("https://ex3.com", "https://ex4.com"));
        list.add(new BannerVO("https://ex5.com", "https://ex6.com"));
        return list;
    }

    private List<ChannelVO> buildChannels() {
        List<ChannelVO> list = new ArrayList<>();
        list.add(new ChannelVO(1L, "https://ex1.com", "标题1"));
        list.add(new ChannelVO(2L, "https://ex2.com", "标题2"));
        list.add(new ChannelVO(3L, "https://ex3.com", "标题3"));
        return list;
    }

    private List<ActivityVO> buildActivities() {
        List<ActivityVO> list = new ArrayList<>();
        list.add(new ActivityVO(1L, "https://ex1.com", "标题"));
        list.add(new ActivityVO(2L, "https://ex2.com", "标题2"));
        list.add(new ActivityVO(3L, "https://ex3.com", "标题3"));
        return list;
    }

    private List<DishItemVO> loadDishes() {
        try {
            List<Dish> dishes = dishService.getAllToAPP(1, null); // 第一页，无关键词
            return dishes.stream()
                    .map(dish -> DishConverter.toDishItemVO(dish, categoryService))
                    .collect(Collectors.toList());
        } catch (Exception e) {
            throw new RuntimeException("Failed to load dish list", e);
        }
    }

    private List<CategoryLevelOneVO> loadCategories() {
        try {
            List<Category> allCategories = categoryService.getAll(null);
            List<Long> levelOneIds = categoryService.getLevelOneIds();
            List<Long> levelTwoIds = categoryService.getLevelTwoIds();

            Map<Long, CategoryLevelOneVO> map = new HashMap<>();
            List<CategoryLevelOneVO> result = new ArrayList<>();

            // 构建一级分类
            for (Category c : allCategories) {
                if (levelOneIds.contains(c.getId())) {
                    CategoryLevelOneVO vo = CategoryConverter.toCategoryLevelOneVO(c);
                    result.add(vo);
                    map.put(c.getId(), vo);
                }
            }

            // 挂载二级分类
            for (Category c : allCategories) {
                if (levelTwoIds.contains(c.getId())) {
                    CategoryLevelOneVO parent = map.get(c.getParentId());
                    if (parent != null) {
                        parent.getChildren().add(CategoryConverter.toCategoryLevelTwoVO(c));
                    }
                }
            }

            return result;
        } catch (Exception e) {
            throw new RuntimeException("Failed to load category list", e);
        }
    }
}